package com.google.code.sapwcrawler.download.cycle;
import java.net.*;
import java.util.*;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicInteger;

public class MultiThreadDownloadCycle extends DownloadCycle
{
	private AtomicInteger counter = new AtomicInteger(0);
	private class Command implements Runnable
	{
		private URL url;
		public Command(URL url)
		{
			this.url = url;
		}
		
		public void run()
		{
			counter.incrementAndGet();
			try
			{
				getDownloadProc().download(url);
			}
			catch(Exception e)
			{
				handleException(e);
			}
			counter.decrementAndGet();
		}
	}
	
	private ExecutorService ex;
	public void setExecutorService(ExecutorService ex)
	{
		this.ex = ex;
	}
	
	private boolean isNobodyDownloading()
	{
		return counter.get() == 0;
	}
	
	@Override
	public void run()
	{
		try
		{
			while(! (getQueue().isEmpty() && isNobodyDownloading()) )
			{
				if(getQueue().isEmpty())
				{
					synchronized (this)
					{
						wait();
					}
				}
				else
				{
					ex.execute(new Command(getQueue().poll()));
				}
			}
			ex.shutdown();
			ex.awaitTermination(2,TimeUnit.MINUTES);
		}
		catch(Throwable e)
		{
			System.out.println(e);
		}
	}
	
	@Override
	public synchronized void addUrl(URL url)
	{
		super.addUrl(url);
		notify();
	}
	
	@Override
	public synchronized void addUrls(List<URL> list)
	{
		super.addUrls(list);
		notify();
	}
}
